import 'dart:async';
import 'dart:convert';

import 'package:flutter/material.dart';
import 'package:http/http.dart' as http;
import 'package:provider/provider.dart';
import 'package:qr_flutter/qr_flutter.dart';

import '../services/audio_service.dart';

class MyPage extends StatefulWidget {

  @override
  _MyPageState createState() => _MyPageState();
}
const String USER_AGENT =
    "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36";

// 定义页面状态
class _MyPageState extends State<MyPage>
    with AutomaticKeepAliveClientMixin {
  @override
  bool get wantKeepAlive => true;
  var limitSeconds = 180;
  var qrcodeKey;
  var qrUrl = '';
  Timer? timer;
  bool showCode = false;
  bool isLogin = false;
  var totalSize;
  var noUseSize;
  dynamic userInfo;

  @override
  void initState() {
    super.initState();
    getUserInfo();
  }

  Future<dynamic> getLoopLoginQuery(String qrcodeKey) async {
    print('qrcodeKey:$qrcodeKey');
    final url = Uri.parse(
        'https://passport.bilibili.com/x/passport-login/web/qrcode/poll?qrcode_key=$qrcodeKey');

    final response = await http.get(url, headers: {'User-Agent': USER_AGENT});

    if (response.statusCode == 200) {
      final String result = response.body;
      final Map<String, String> headers = response.headers;
      String? cookie;
      if (headers.containsKey('set-cookie')) {
        cookie = headers['set-cookie']!;
      }
      final Map<String, dynamic> responseData = {
        'result': result,
        'cookie': cookie,
      };
      return responseData;
    } else {
      throw Exception('Failed to load data: ${response.statusCode}');
    }
  }

  String? _getHostFromUrl(String url) {
    if (url.isEmpty) {
      return '';
    }
    RegExp regex = RegExp(r'(?<=\/\/).*?(?=\/)');
    Match match = regex.firstMatch(url) as Match;
    String? host = match.group(0);
    print('host:$host');
    return host;
  }

  Future<dynamic> get_login_png_url() async {
    const String url =
        "https://passport.bilibili.com/x/passport-login/web/qrcode/generate";
    final cidResponse = await http.get(Uri.parse(url), headers: {
      'user-agent': USER_AGENT,
    });
    return jsonDecode(cidResponse.body);
  }

  Future<dynamic> getUserInfo() async {
    final audioService = Provider.of<AudioService>(context, listen: true);
    final cookie = audioService.cookie;
    const String url = "https://api.bilibili.com/x/web-interface/nav";
    final res = await http.get(Uri.parse(url), headers: {
      'user-agent': USER_AGENT,
      'cookie': cookie
    });
    final result = jsonDecode(res.body);
    if (result['code'] == 0) {
      audioService.setLogin(true);
      setState(() {
        userInfo = result['data'];
      });
    } else {
      audioService.setLogin(false);
    }
  }

  void handleScanCode() async {
    if (showCode) {
      return;
    }
    final jsonResult = await get_login_png_url();
    setState(() {
      limitSeconds = 180;
    });
    setState(() {
      qrcodeKey = jsonResult['data']['qrcode_key'];
      qrUrl = jsonResult['data']['url'];
      showCode = true;
    });
    loopQueryLogin();
  }

  void loopQueryLogin() async {
    if (timer != null) {
      timer?.cancel();
    }
    final audioService = Provider.of<AudioService>(context, listen: true);
    timer = Timer.periodic(Duration(seconds: 1), (timer) async {
      final parseResult = await getLoopLoginQuery(qrcodeKey);
      final res = json.decode(parseResult['result']);
      final code = res['data']['code'];
      final msg = res['data']['message'];
      final cookie = parseResult['cookie'];
      print({'msg': msg});
      if (code == 0) {
        timer.cancel();
        // message.success('登录成功!');
        // Fluttertoast.showToast(
        //     msg: "登录成功!",
        //     toastLength: Toast.LENGTH_SHORT,
        //     gravity: ToastGravity.CENTER,
        //     timeInSecForIosWeb: 1,f
        //     backgroundColor: Colors.grey,
        //     textColor: Colors.white,
        //     fontSize: 16.0
        // );
        setState(() {
          showCode = false;
        });
        audioService.setCookie(cookie);
        Future.delayed(Duration(milliseconds: 200), () {
          // store.getUserInfo();
          getUserInfo();
        });
      } else {
        if (msg != '未扫码') {
          // Fluttertoast.showToast(
          //     msg:msg,
          //     toastLength: Toast.LENGTH_SHORT,
          //     gravity: ToastGravity.CENTER,
          //     timeInSecForIosWeb: 1,
          //     backgroundColor: Colors.grey,
          //     textColor: Colors.white,
          //     fontSize: 16.0
          // );
        }
      }
      if (limitSeconds > 0) {
        setState(() {
          limitSeconds -= 1;
          print({'limitSeconds': limitSeconds});
        });
      } else {
        timer.cancel();
        // handleScanCode();
        // Fluttertoast.showToast(
        //     msg:'二维码已过期,请更新二维码',
        //     toastLength: Toast.LENGTH_SHORT,
        //     gravity: ToastGravity.CENTER,
        //     timeInSecForIosWeb: 1,
        //     backgroundColor: Colors.grey,
        //     textColor: Colors.white,
        //     fontSize: 16.0
        // );
        setState(() {
          limitSeconds = 180;
          showCode = false;
        });
      }
      print({'parseResult': parseResult});
    });
  }

  String byte2Txt(dynamic size) {
    if (size == null) {
      return '';
    }
    const List<String> unitArr = [
      'B',
      'KB',
      'MB',
      'GB',
      'TB',
      'PB',
      'EB',
      'ZB',
      'YB',
      'BB'
    ];
    int count = 0;
    double newSize = size.toDouble();

    // 循环直到 newSize 小于或等于 1024
    while (newSize > 1024) {
      newSize /= 1024;
      count++;

      // 确保不超出 unitArr 的长度
      if (count >= unitArr.length) {
        break;
      }
    }

    // 使用 String.format 格式化 newSize 到两位小数
    return newSize.toStringAsFixed(2) + unitArr[count];
  }

  @override
  Widget build(BuildContext context) {
    return SingleChildScrollView(
        padding: EdgeInsets.only(bottom: 50),
        child: Column(
          children: [
            SizedBox(height: 10),
            Row(
              children: [
                SizedBox(width: 20),
                SizedBox(width: 20),
                Text('已缓存:${byte2Txt(totalSize)}',
                    style: TextStyle(fontSize: 14)),
                SizedBox(width: 20),
                Text('无用缓存:${byte2Txt(noUseSize)}',
                    style: TextStyle(fontSize: 14)),
              ],
            ),
            SizedBox(height: 8),
            showCode
                ? QrImageView(
              data: qrUrl,
              version: QrVersions.auto,
              backgroundColor: Colors.white,
              size: 100.0,
            )
                : SizedBox(),
            showCode
                ? Text('请打开Bilibili客户端扫码登录,$limitSeconds秒过期',
                style: TextStyle(fontSize: 14))
                : SizedBox(),
            Row(
              children: [
                SizedBox(width: 20),
                !context.watch<AudioService>().isLogin
                    ? ElevatedButton(
                  onPressed: () async {
                    handleScanCode();
                  },
                  child: Text('登录Bilibili'),
                )
                    : SizedBox(),
                context.watch<AudioService>().isLogin && userInfo != null
                    ? FadeInImage(
                    placeholder: AssetImage('assets/placeholder.png'),
                    image: NetworkImage(
                      userInfo['face'],
                      headers: {
                        'host': _getHostFromUrl(userInfo['face'])!,
                        'Referer': 'https://bilibili.com'
                      },
                    ),
                    fit: BoxFit.cover,
                    width: 40,
                    height: 40)
                    : SizedBox(),
                SizedBox(width: 8),
                context.watch<AudioService>().isLogin
                    ? Text(userInfo?['uname'] ?? '')
                    : SizedBox(),
                SizedBox(width: 8),
                context.watch<AudioService>().isLogin
                    ? Text('已登录', style: TextStyle(fontSize: 14))
                    : SizedBox(),
                SizedBox(width: 8),
                context.watch<AudioService>().isLogin
                    ? ElevatedButton(
                  onPressed: () async {
                    context.read<AudioService>().setLogin(false);
                    userInfo = null;
                    context.read<AudioService>().setCookie('');
                  },
                  child: Text('注销登录'),
                )
                    : SizedBox(),
              ],
            ),
          ],
        ));
  }
}


